/*
 * Copyright (c) 2008  Jonhnny Weslley
 * 
 * This program is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License as published by the Free
 * Software Foundation; either version 2 of the License, or (at your option)
 * any later version.
 * 
 * This program is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
 * more details.
 * 
 * You should have received a copy of the GNU General Public License along with
 * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
 * Place, Suite 330, Boston, MA 02111-1307 USA
 */
package easyaccept.maven;

import java.io.File;

import org.apache.maven.plugin.AbstractMojo;
import org.apache.maven.plugin.MojoExecutionException;
import org.apache.maven.plugin.MojoFailureException;
import org.apache.maven.project.MavenProject;
import org.codehaus.plexus.util.DirectoryScanner;

/**
 * Run tests using EasyAccept.
 * 
 * @phase test
 * @goal run
 * @requiresDependencyResolution test
 * @author Jonhnny Weslley
 */
public class EasyAcceptMojo extends AbstractMojo {

	/**
	 * Maven project.
	 * 
	 * @parameter expression="${project}"
	 * @required
	 * @readonly
	 */
	protected MavenProject project;

	/**
	 * Jvm Arguments.
	 * 
	 * @parameter
	 */
	protected String[] jvmArgs;

	/**
	 * ClassName (FQN) of the EasyAccept tool to provide.
	 * 
	 * @required
	 * @parameter expression="${maven.easyaccept.className}"
	 *            default-value="easyaccept.EasyAccept"
	 */
	protected String easyAcceptClassName;

	/**
	 * ClassName (FQN) of the facade class required by the EasyAccept tool.
	 * 
	 * @required
     * @parameter expression="${facadeClass}"
     */
	protected String facadeClass;

	/**
	 * The directory containing the script files of the project being tested.
	 * 
	 * @parameter expression="${project.build.testSourceDirectory}/../easyaccept"
	 */
	protected File testSourceDir;

	/**
	 * The pattern used to specify the script files that should be included in testing.
	 * When not specified the default will be "*", indicating that all files should be included.
	 * 
	 * @required
	 * @parameter expression="${pattern}" default-value="*"
	 */
	protected String pattern;

	/**
	 * Option to print the java command used in testing.
	 * 
	 * @required
	 * @parameter expression="${maven.easyAccept.displayCommand}" default-value="false"
	 */
	protected boolean displayCommand;

	public final void execute() throws MojoExecutionException, MojoFailureException {
		try {
			doExecute();
		} catch (MojoExecutionException e) {
			throw e;
		} catch (MojoFailureException e) {
			throw e;
		} catch (RuntimeException e) {
			throw e;
		} catch (Exception e) {
			throw new MojoExecutionException("wrap: " + e, e);
		}
	}

	protected void doExecute() throws Exception {
		JavaCommand javaCommand = new JavaCommand(this, easyAcceptClassName);
		javaCommand
			.addJvmArgs(jvmArgs)
			.addClasspath(project.getTestClasspathElements())
			.addArgs(facadeClass)
			.addArgs(findFiles())
			.run(displayCommand);
	}

	private String[] findFiles() {
		String testSource = testSourceDir.getAbsolutePath();
		String[] files = findFiles(testSourceDir, pattern);
		for (int i = 0; i < files.length; i++) {
			files[i] = testSource + File.separator + files[i];
		}
		return files;
	}

	private String[] findFiles(File dir, String pattern) {
		final DirectoryScanner scanner = new DirectoryScanner();
		scanner.setBasedir(dir);
		scanner.setIncludes(new String[] { pattern });
		scanner.addDefaultExcludes();
		scanner.scan();
		return scanner.getIncludedFiles();
	}

}
